package stud.cp.user.plugins.designer;

import java.math.BigInteger;
import java.util.List;

import javax.ejb.Stateless;
import javax.servlet.http.HttpServletRequest;

import org.apache.log4j.Logger;

import stud.cp.core.dbaccess.DAOException;
import stud.cp.core.plugins.PluginConst;
import stud.cp.core.plugins.PluginRouter;
import stud.cp.core.plugins.WrongPageRequest;
import stud.cp.user.dbaccess.OracleDAOFactory;
import stud.cp.user.valueobjects.DBObjectType;

/**
 * Имплементация логики работы с типами продуктов.
 */
@Stateless
public class ProductTypesPluginBean implements ProductTypesPluginBeanLocal {

	/**
	 * Фабрика DAO классов.
	 */
	private OracleDAOFactory oracleDAOFactory = null;
	/**
	 * Логгер.
	 */
	private static Logger logger = Logger.getLogger("ACPII");

	/**
	 * Метод, выполняющий бизнес логику плагина.
	 *
	 * @param req Реквест.
	 * @return Класс плагин.
	 */
	@Override
	public PluginRouter perform(HttpServletRequest req) {
		String subaction = req.getParameter(PluginConst.SUBACTION);


		if ((subaction != null) && (!subaction.equals(""))) {
			try {

				oracleDAOFactory = new OracleDAOFactory();
				oracleDAOFactory.initialize();
				/*
				 * Список действий которые могут выполниться.
				 */

				if (subaction.equals(PluginConst.GET_LIST)) {
					return getListOfProductTypes(req);
				}

				/*
				 * Страница добавления
				 */
				if (subaction.equals(PluginConst.GET_ADD_PAGE)) {
					return getAddPage(req);
				}

				/*
				 * Добавление новых данных
				 */
				if (subaction.equals(PluginConst.NEW_DATA)) {
					return newData(req);
				}

				/*Страница редактирования*/
				if (subaction.equals(PluginConst.GET_EDIT_PAGE)) {
					return getEditPage(req);
				}

				/*Сохранение измененных данных*/
				if (subaction.equals(PluginConst.SAVE_DATA)) {
					return saveData(req);
				}

				/*Страница удаления*/
				if (subaction.equals(PluginConst.GET_DELETE_PAGE)) {
					return getDeletePage(req);
				}

				/*Удаление данные*/
				if (subaction.equals(PluginConst.DELETE_DATA)) {
					return deleteData(req);
				}
				//
				//                /*Страница просмотра данных о типе оружия*/
				//                if (subaction.equals(PluginConst.GET_VIEW_PAGE)) {
				//                    return getViewPage(req);
				//                }
				//
				//                /*Страница со списком свойств, принадлежащий данному типу оружия.*/
				//                if (subaction.equals(PluginConst.GET_WEAPON_TYPE_PROPERTIES_LIST)) {
				//                    return getObjectTypePropertyListPage(req);
				//                }
				//
				//                /*Страница с диалогом для пользователя, который хочет исключить свойство из типа оружия.*/
				//                if (subaction.equals(PluginConst.EXCLUDE_PROPERTY_FROM_WEAPON_TYPE_PAGE)) {
				//                    return getExcludePropertyFromObjectTypePage(req);
				//                }
				//
				//                /*Исключение свойства из объектного типа.*/
				//                if (subaction.equals(PluginConst.EXCLUDE_PROPERTY_FROM_WEAPON_TYPE)) {
				//                    return excludePropertyFromObjectType(req);
				//                }
				//
				//                /*Страница добавления свойств к типу оружия.*/
				//                if (subaction.equals(PluginConst.ADD_PROPERTIES_TO_WEAPON_TYPE_PAGE)) {
				//                    return getAddPropertiesToObjectTypePage(req);
				//                }
				//
				//                /*Добавление свойств к объектному типу*/
				//                if (subaction.equals(PluginConst.ADD_PROPERTIES_TO_WEAPON_TYPE)) {
				//                    return addPropertiesToObjectType(req);
				//                }

				req.setAttribute(PluginConst.ERROR_MESSAGE,
						"Действия для данного типа поддействия не найдено. Тип поддействия = " + subaction);
			} catch (DAOException ex) {
				logger.debug("Error due access to database. "
						+ "Plugin = ProductTypesPluginBean. "
						+ "Subaction=" + subaction, ex);
				req.setAttribute(PluginConst.ERROR_MESSAGE,
						"Ошибка доступа к базе данных " + ex.getMessage());
			} catch (WrongPageRequest ex) {
				req.setAttribute(PluginConst.ERROR_MESSAGE,
						"Данные из реквеста ошибочны :\n" + ex.getMessage());
			} catch(NumberFormatException ex){
				req.setAttribute(PluginConst.ERROR_MESSAGE,
						"ID объекта не имеет числовой формат :\n" + ex.getMessage());
			}finally {

				if (oracleDAOFactory != null) {
					try {
						oracleDAOFactory.cleanUp();
					} catch (DAOException ex) {
						logger.debug("Error due access to database. "
								+ "Plugin = ProductTypesPluginBean. "
								+ "Subaction=" + subaction, ex);
						req.setAttribute(PluginConst.ERROR_MESSAGE,
								"Ошибка доступа к базе данных " + ex.getMessage());
					}
				}
			}
		} else {
			req.setAttribute(PluginConst.ERROR_MESSAGE,
					"Тип поддействия не задан.");
		}

		return new PluginRouter("/errorpage.jsp");
	}

	private PluginRouter getListOfProductTypes(HttpServletRequest req) throws DAOException, WrongPageRequest {
		List<DBObjectType> listOfDBObjectTypes =
				oracleDAOFactory.getObjectTypesDAO().getObjectTypeHeirs(PluginConst.PRODUCTS_OBJECT_TYPE_ID);
		req.setAttribute(DesignerPluginConst.OBJECT_TYPE_LIST, listOfDBObjectTypes);
		return new PluginRouter("/Designer/ProductTypes/ProductTypesTable.jsp");
	}

	//    List<DBObject> listOfDBObjects =
	//            oracleDAOFactory.getObjectDAO().getAllObjectByObjectType(objectTypeId);
	//    req.setAttribute(DesignerPluginConst.OBJECT_HEIRS_LIST, listOfDBObjects);
	//    return new PluginRouter("/Designer/Products/ProductsTable.jsp");

	private PluginRouter getAddPage(HttpServletRequest req) throws DAOException, WrongPageRequest {
		return new PluginRouter("/Designer/ProductTypes/AddProductType.jsp");
	}

	/**
	 * Метод, позволяющий добавлять новые данные.
	 *
	 * @param req Реквест.
	 * @return PluginRouter c запрашиваемой страницей.
	 * @throws DAOException Ошибка доступа к базе данных.
	 * @throws WrongPageRequest Критическая ошибка в данных реквеста.
	 */
	private PluginRouter newData(HttpServletRequest req) throws DAOException, WrongPageRequest {
		String name = req.getParameter(PluginConst.OBJECT_TYPE_NAME);
		String description = req.getParameter(PluginConst.OBJECT_TYPE_DESCRIPTION);

		BigInteger object_type_id = oracleDAOFactory.getObjectTypesDAO().
				create(new DBObjectType(name, description, PluginConst.PRODUCTS_OBJECT_TYPE_ID, false));

		//TODO::Вернуть страницу с листом продуктов для данного типа.
		return new PluginRouter("product-types-action.do"
				+ "?"
				+ PluginConst.SUBACTION
				+ "="
				+ PluginConst.GET_LIST, false);
	}

	/**
	 * Метод, который позволяет
	 * перейти на страницу удаления элемента.
	 * @param req Реквест.
	 * @return PluginRouter c запрашиваемой страницей.
	 * @throws DAOException Ошибка доступа к базе данных.
	 * @throws WrongPageRequest Критическая ошибка в данных реквеста.
	 */
	private PluginRouter getDeletePage(HttpServletRequest req) throws DAOException, WrongPageRequest { 	
		String objectTypeIdValue=req.getParameter(PluginConst.OBJECT_TYPE_ID);
		if((objectTypeIdValue==null)||(objectTypeIdValue.equals(""))){
			throw new WrongPageRequest("ID объекта не занад!");
		}
		BigInteger objectTypeId =
				new BigInteger(objectTypeIdValue);
		DBObjectType objectType = oracleDAOFactory.getObjectTypesDAO().getById(objectTypeId);
		if (objectType != null) {
			req.setAttribute(PluginConst.OBJECT_TYPE, objectType);
			return new PluginRouter("/Designer/ProductTypes/DeleteProductType.jsp");
		} else {
			throw new WrongPageRequest("Тип оружия с таким id=" + objectTypeId + " не существует. ");
		}

	}


	/**
	 * Метод, удаляющий данные из базы данных.
	 * @param req Реквест.
	 * @return PluginRouter c запрашиваемой страницей.
	 * @throws DAOException Ошибка доступа к базе данных.
	 * @throws WrongPageRequest Критическая ошибка в данных реквеста.
	 */
	private PluginRouter deleteData(HttpServletRequest req) throws DAOException, WrongPageRequest {
		String objectTypeIdValue=req.getParameter(PluginConst.OBJECT_TYPE_ID);
		if((objectTypeIdValue==null)||(objectTypeIdValue.equals(""))){
			throw new WrongPageRequest("ID объекта не занад!");
		}
		BigInteger objectTypeId =
				new BigInteger(objectTypeIdValue);

		DBObjectType objectType = oracleDAOFactory.getObjectTypesDAO().getById(objectTypeId);
		if (objectType != null) {
			oracleDAOFactory.getObjectTypesDAO().delete(objectType.getObject_type_id());
			return new PluginRouter("product-types-action.do"
					+ "?"
					+ PluginConst.SUBACTION
					+ "="
					+ PluginConst.GET_LIST, false);
		} else {
			throw new WrongPageRequest("Тип оружия с таким id=" + objectTypeId + " не существует. ");
		}

	}

	/**
	 * Метод, который позволяет
	 * перейти на страницу редактирования данных.
	 * @param req Реквест.
	 * @return PluginRouter c запрашиваемой страницей.
	 * @throws DAOException Ошибка доступа к базе данных.
	 * @throws WrongPageRequest Критическая ошибка в данных реквеста.
	 */
	private PluginRouter getEditPage(HttpServletRequest req) throws DAOException, WrongPageRequest {
		String objectTypeIdValue=req.getParameter(PluginConst.OBJECT_TYPE_ID);
		if((objectTypeIdValue==null)||(objectTypeIdValue.equals(""))){
			throw new WrongPageRequest("ID объекта не занад!");
		}
		BigInteger objectTypeId =
				new BigInteger(objectTypeIdValue);

		DBObjectType objectType = oracleDAOFactory.getObjectTypesDAO().getById(objectTypeId);
		if (objectType != null) {
			req.setAttribute(PluginConst.OBJECT_TYPE, objectType);
			return new PluginRouter("/Designer/ProductTypes/EditProductType.jsp");
		} else {
			throw new WrongPageRequest("Тип оружия с таким id=" + objectTypeId + " не существует. ");
		}

	}

	/**
	 * Сохранение данных.
	 * @param req Реквест.
	 * @return PluginRouter c запрашиваемой страницей.
	 * @throws DAOException Ошибка доступа к базе данных.
	 * @throws WrongPageRequest Критическая ошибка в данных реквеста.
	 */
	private PluginRouter saveData(HttpServletRequest req) throws DAOException, WrongPageRequest {
		String name = req.getParameter(PluginConst.OBJECT_TYPE_NAME);
		String description = req.getParameter(PluginConst.OBJECT_TYPE_DESCRIPTION);
		String objectTypeIdValue=req.getParameter(PluginConst.OBJECT_TYPE_ID);
		logger.debug("Test = "+objectTypeIdValue);
		if((objectTypeIdValue==null)||(objectTypeIdValue.equals(""))){
			throw new WrongPageRequest("ID объекта не занад!");
		}
		BigInteger objectTypeId =
				new BigInteger(objectTypeIdValue);

		DBObjectType objectType = oracleDAOFactory.getObjectTypesDAO().getById(objectTypeId);
		if (objectType != null) {
			objectType.setName(name);
			objectType.setDescription(description);
			oracleDAOFactory.getObjectTypesDAO().update(objectType);
			return new PluginRouter("product-types-action.do"
					+ "?"
					+ PluginConst.SUBACTION
					+ "="
					+ PluginConst.GET_LIST, false);
		} else {
			throw new WrongPageRequest("Тип оружия с таким id=" + objectTypeId + " не существует. ");
		}

	}


}
